package com.wpw.dream.nio;

import java.io.IOException;
import java.net.InetSocketAddress;
import java.nio.ByteBuffer;
import java.nio.channels.ClosedChannelException;
import java.nio.channels.SelectionKey;
import java.nio.channels.Selector;
import java.nio.channels.SocketChannel;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.Scanner;
import java.util.Set;

public class NIOClient {
	
	private SocketChannel client;
	
	private Selector selector;
	
	private ByteBuffer recBuffer;
	
	private ByteBuffer sendBuffer;
	
	Map<SelectionKey, String> map = new HashMap<>(); 
	
	public NIOClient() {
		try {
			client = SocketChannel.open();
			client.configureBlocking(false);
			
			selector = Selector.open();
			
			recBuffer = ByteBuffer.allocate(1024);
			sendBuffer = ByteBuffer.allocate(1024);
		} catch (ClosedChannelException e) {
			e.printStackTrace();
		} catch (IOException e) {
			e.printStackTrace();
		}
	}
	
	public void session(String host, int port) {
		try {
			client.connect(new InetSocketAddress(host, port));
			
			client.register(selector, SelectionKey.OP_CONNECT);
			
			
			if (client.isConnectionPending()) {
				client.finishConnect();
			}
			client.register(selector, SelectionKey.OP_WRITE);
			
			Scanner sc = new Scanner(System.in); 
			while (sc.hasNextLine()) {
				String line = sc.nextLine();
				if (line.equals("finish")) {
					System.exit(0);
				}
				
				Boolean flag = true;
				while (flag) {
					
					int count = selector.select();
					if (count == 0) {
						continue;
					}
					Set<SelectionKey> keys = selector.selectedKeys();
					Iterator<SelectionKey> iterator = keys.iterator();
					while (iterator.hasNext()) {
						SelectionKey key = iterator.next();
						
						if (key.isValid() && key.isWritable()) {
							sendBuffer.clear();
							sendBuffer.put(line.getBytes());
							
							sendBuffer.flip();
							client.write(sendBuffer);
							client.register(selector, SelectionKey.OP_READ);
							
							
						} else if (key.isValid() && key.isReadable()) {
							
							recBuffer.clear();
							int len = client.read(recBuffer);
							if (len > 0) {
								
								String msg = new String(recBuffer.array(), 0, len);
								System.out.println(msg);
							}
							client.register(selector, SelectionKey.OP_WRITE);
							flag = false;
						}
						
						iterator.remove();
					}
				}
				
				
			}
			
		} catch (IOException e) {
			e.printStackTrace();
		}
	}
	
	/*private void process(SelectionKey key) {
		if (key.isValid() && key.is)
	}*/

	public static void main(String[] args) {
		new NIOClient().session("127.0.0.1", 8091);
	}

}
